{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# numpy: Broadcasting"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "metadata": {
    "collapsed": false
   },
   "outputs": [],
   "source": [
    "import numpy as np"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "(3, 3)\n",
      "[[0 1 2]\n",
      " [3 4 5]\n",
      " [6 7 8]]\n",
      "(3, 3)\n",
      "[[ 4  5  6]\n",
      " [ 7  8  9]\n",
      " [10 11 12]]\n"
     ]
    }
   ],
   "source": [
    "a = np.arange(9).reshape(3, 3)\n",
    "print(a.shape)\n",
    "print(a)\n",
    "b = np.arange(4, 4+9).reshape(3, 3)\n",
    "print(b.shape)\n",
    "print(b)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "array([[ 4,  6,  8],\n",
       "       [10, 12, 14],\n",
       "       [16, 18, 20]])"
      ]
     },
     "execution_count": 3,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "#clear\n",
    "a+b"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "So this is easy and one-to-one.\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "---\n",
    "\n",
    "What if the shapes do not match?"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "(3, 3)\n",
      "[[0 1 2]\n",
      " [3 4 5]\n",
      " [6 7 8]]\n",
      "(3,)\n",
      "[0 1 2]\n"
     ]
    }
   ],
   "source": [
    "a = np.arange(9).reshape(3, 3)\n",
    "print(a.shape)\n",
    "print(a)\n",
    "b = np.arange(3)\n",
    "print(b.shape)\n",
    "print(b)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "What will this do?"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "array([[ 0,  2,  4],\n",
       "       [ 3,  5,  7],\n",
       "       [ 6,  8, 10]])"
      ]
     },
     "execution_count": 5,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "a+b"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "It has *broadcast* along the last axis!"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "---\n",
    "\n",
    "Can we broadcast along the *first* axis?"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "array([[ 0,  1,  2],\n",
       "       [ 4,  5,  6],\n",
       "       [ 8,  9, 10]])"
      ]
     },
     "execution_count": 6,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "#clear\n",
    "a+b.reshape(3, 1)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Rules:\n",
    "\n",
    "* Shapes are matched axis-by-axis from last to first.\n",
    "* A length-1 axis can be *broadcast* if necessary."
   ]
  }
 ],
 "metadata": {},
 "nbformat": 4,
 "nbformat_minor": 0
}